home *** CD-ROM | disk | FTP | other *** search
/ InterCD 2000 September / september_2000.iso / intercd / root / ^Linux / WindowMaker / WINGs / findfile.c < prev    next >
Encoding:
C/C++ Source or Header  |  1999-10-09  |  6.7 KB  |  347 lines

  1. /*
  2.  *  Window Maker miscelaneous function library
  3.  * 
  4.  *  Copyright (c) 1997 Alfredo K. Kojima
  5.  * 
  6.  *  This program is free software; you can redistribute it and/or modify
  7.  *  it under the terms of the GNU General Public License as published by
  8.  *  the Free Software Foundation; either version 2 of the License, or
  9.  *  (at your option) any later version.
  10.  *
  11.  *  This program is distributed in the hope that it will be useful,
  12.  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
  13.  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  14.  *  GNU General Public License for more details.
  15.  *
  16.  *  You should have received a copy of the GNU General Public License
  17.  *  along with this program; if not, write to the Free Software
  18.  *  Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  19.  */
  20.  
  21.  
  22. #include "../src/config.h"
  23.  
  24. #include "WUtil.h"
  25.  
  26. #include <stdlib.h>
  27. #include <unistd.h>
  28. #include <string.h>
  29. #include <pwd.h>
  30. #include <limits.h>
  31.  
  32. #ifndef PATH_MAX
  33. #define PATH_MAX  1024
  34. #endif
  35.  
  36.  
  37. char*
  38. wgethomedir()
  39. {
  40.     char *home = getenv("HOME");
  41.     struct passwd *user;
  42.  
  43.     if (home)
  44.       return home;
  45.     
  46.     user = getpwuid(getuid());
  47.     if (!user) {
  48.     wsyserror("could not get password entry for UID %i", getuid());
  49.     return "/";
  50.     }
  51.     if (!user->pw_dir) {
  52.     return "/";
  53.     } else {
  54.     return user->pw_dir;
  55.     }
  56. }
  57.  
  58.  
  59. static char*
  60. getuserhomedir(char *username)
  61. {
  62.     struct passwd *user;
  63.     
  64.     user = getpwnam(username);
  65.     if (!user) {
  66.     wsyserror("could not get password entry for user %s", username);
  67.     return NULL;
  68.     }
  69.     if (!user->pw_dir) {
  70.     return "/";
  71.     } else {
  72.     return user->pw_dir;
  73.     }
  74. }
  75.  
  76.  
  77.  
  78.  
  79. char*
  80. wexpandpath(char *path)
  81. {
  82.     char buffer2[PATH_MAX+2];
  83.     char buffer[PATH_MAX+2];
  84.     int i;
  85.  
  86.     memset(buffer, 0, PATH_MAX+2);
  87.     
  88.     if (*path=='~') {
  89.     char *home;
  90.     
  91.     path++;
  92.     if (*path=='/' || *path==0) {
  93.         home = wgethomedir();
  94.         strcat(buffer, home);
  95.     } else {
  96.         int j;
  97.         j = 0;
  98.         while (*path!=0 && *path!='/') {
  99.         buffer2[j++] = *path;
  100.         buffer2[j] = 0;
  101.         path++;
  102.         }
  103.         home = getuserhomedir(buffer2);
  104.         if (!home)
  105.         return NULL;
  106.         strcat(buffer, home);
  107.     }
  108.     }
  109.     
  110.     i = strlen(buffer);
  111.  
  112.     while (*path!=0) {
  113.     char *tmp;
  114.     
  115.     if (*path=='$') {
  116.         int j = 0;
  117.         path++;
  118.         /* expand $(HOME) or $HOME style environment variables */
  119.         if (*path=='(') {
  120.         path++;
  121.         while (*path!=0 && *path!=')') {
  122.             buffer2[j++] = *(path++);
  123.             buffer2[j] = 0;
  124.                 }
  125.                 if (*path==')')
  126.                     path++;
  127.         tmp = getenv(buffer2);
  128.         if (!tmp) {
  129.             buffer[i] = 0;
  130.             strcat(buffer, "$(");
  131.             strcat(buffer, buffer2);
  132.             strcat(buffer, ")");
  133.             i += strlen(buffer2)+3;
  134.         } else {
  135.             strcat(buffer, tmp);
  136.             i += strlen(tmp);
  137.         }
  138.         } else {
  139.         while (*path!=0 && *path!='/') {
  140.             buffer2[j++] = *(path++);
  141.             buffer2[j] = 0;
  142.         }
  143.         tmp = getenv(buffer2);
  144.         if (!tmp) {
  145.             strcat(buffer, "$");
  146.             strcat(buffer, buffer2);
  147.             i += strlen(buffer2)+1;
  148.         } else {
  149.             strcat(buffer, tmp);
  150.             i += strlen(tmp);
  151.         }
  152.         }        
  153.     } else {
  154.         buffer[i++] = *path;
  155.         path++;
  156.     }
  157.     }
  158.     
  159.     return wstrdup(buffer);
  160. }
  161.  
  162.  
  163.  
  164. /*
  165.  *----------------------------------------------------------------------
  166.  * findfile--
  167.  *     Finds a file in a : separated list of paths. ~ expansion is also 
  168.  * done.
  169.  * 
  170.  * Returns:
  171.  *     The complete path for the file (in a newly allocated string) or
  172.  * NULL if the file was not found.
  173.  * 
  174.  * Side effects:
  175.  *     A new string is allocated. It must be freed later.
  176.  * 
  177.  *---------------------------------------------------------------------- 
  178.  */
  179. char*
  180. wfindfile(char *paths, char *file)
  181. {
  182.     char *path;
  183.     char *tmp;
  184.     int done;
  185.     int len, flen;
  186.     char *fullpath;
  187.  
  188.     if (!file)
  189.     return NULL;
  190.     
  191.     if (*file=='/' || *file=='~' || *file=='$' || !paths) {
  192.     if (access(file, F_OK)<0) {
  193.         fullpath = wexpandpath(file);
  194.         if (!fullpath)
  195.         return NULL;
  196.         
  197.         if (access(fullpath, F_OK)<0) {
  198.         wfree(fullpath);
  199.         return NULL;
  200.         } else {
  201.         return fullpath;
  202.         }
  203.     } else {
  204.         return wstrdup(file);
  205.     }
  206.     }
  207.  
  208.     flen = strlen(file);
  209.     tmp = paths;
  210.     done = 0;
  211.     while (!done) {
  212.     len = strcspn(tmp, ":");
  213.     if (len==0) done=1;
  214.     path = wmalloc(len+flen+2);
  215.     path = memcpy(path, tmp, len);
  216.     path[len]=0;
  217.     strcat(path, "/");
  218.     strcat(path, file);
  219.     fullpath = wexpandpath(path);
  220.     wfree(path);
  221.     if (fullpath) {
  222.         if (access(fullpath, F_OK)==0) {
  223.         return fullpath;
  224.         }
  225.         wfree(fullpath);
  226.     }
  227.     tmp=&(tmp[len+1]);
  228.     if (*tmp==0) break;
  229.     }
  230.     return NULL;
  231. }
  232.  
  233.  
  234. char*
  235. wfindfileinlist(char **path_list, char *file)
  236. {
  237.     int i;
  238.     char *path;
  239.     int len, flen;
  240.     char *fullpath;
  241.  
  242.     if (!file)
  243.     return NULL;
  244.     
  245.     if (*file=='/' || *file=='~' || !path_list) {
  246.     if (access(file, F_OK)<0) {
  247.         fullpath = wexpandpath(file);
  248.         if (!fullpath)
  249.         return NULL;
  250.         
  251.         if (access(fullpath, F_OK)<0) {
  252.         wfree(fullpath);
  253.         return NULL;
  254.         } else {
  255.         return fullpath;
  256.         }
  257.     } else {
  258.         return wstrdup(file);
  259.     }
  260.     }
  261.  
  262.     flen = strlen(file);
  263.     for (i=0; path_list[i]!=NULL; i++) {
  264.     len = strlen(path_list[i]);
  265.     path = wmalloc(len+flen+2);
  266.     path = memcpy(path, path_list[i], len);
  267.     path[len]=0;
  268.     strcat(path, "/");
  269.     strcat(path, file);
  270.     /* expand tilde */
  271.     fullpath = wexpandpath(path);
  272.     wfree(path);
  273.     if (fullpath) {
  274.         /* check if file exists */
  275.         if (access(fullpath, F_OK)==0) {
  276.         return fullpath;
  277.         }
  278.         wfree(fullpath);
  279.     }
  280.     }
  281.     return NULL;
  282. }
  283.  
  284.  
  285.  
  286. char*
  287. wfindfileinarray(proplist_t array, char *file)
  288. {
  289.     int i;
  290.     char *path;
  291.     int len, flen;
  292.     char *fullpath;
  293.  
  294.     if (!file)
  295.     return NULL;
  296.     
  297.     if (*file=='/' || *file=='~' || !array) {
  298.     if (access(file, F_OK)<0) {
  299.         fullpath = wexpandpath(file);
  300.         if (!fullpath)
  301.         return NULL;
  302.  
  303.         if (access(fullpath, F_OK)<0) {
  304.         wfree(fullpath);
  305.         return NULL;
  306.         } else {
  307.         return fullpath;
  308.         }
  309.     } else {
  310.         return wstrdup(file);
  311.     }
  312.     }
  313.  
  314.     flen = strlen(file);
  315.     for (i=0; i<PLGetNumberOfElements(array); i++) {
  316.     proplist_t prop;
  317.     char *p;
  318.  
  319.     prop = PLGetArrayElement(array, i);
  320.     if (!prop)
  321.         continue;
  322.     p = PLGetString(prop);
  323.  
  324.     len = strlen(p);
  325.     path = wmalloc(len+flen+2);
  326.     path = memcpy(path, p, len);
  327.     path[len]=0;
  328.     strcat(path, "/");
  329.     strcat(path, file);
  330.     /* expand tilde */
  331.     fullpath = wexpandpath(path);
  332.     wfree(path);
  333.     if (fullpath) {
  334.         /* check if file exists */
  335.         if (access(fullpath, F_OK)==0) {
  336.         return fullpath;
  337.         }
  338.         wfree(fullpath);
  339.     }
  340.     }
  341.     return NULL;
  342. }
  343.  
  344.  
  345.  
  346.  
  347.